<?php
/*
 * @Author: CHINAKAIYUAN<sunkaiyuan@namenode.cn>
 * @Date: 2022-02-04 16:53:56
 * @LastEditTime: 2023-11-07 13:30:23
 * @LastEditors: 孙开源 && sunkaiyuan@namenode.cn
 * @Description: 
 */

namespace App\Http\Services\Purchase;


use App\Http\Services\Service;
use App\Repositories\ProOutsourcingDeliveryRepository;
use App\Repositories\PurchaseStorageDetailsRepository;
use App\Repositories\PurchaseStorageRepository;
use Illuminate\Database\Eloquent\Model;

/**
 * Summary of StorageService
 * @property ProOutsourcingDeliveryRepository $proOutsourcing
 * @author sunkaiyuan
 */
class StorageService extends Service
    {
    public $details;
    public function boot(PurchaseStorageRepository $repository, PurchaseStorageDetailsRepository $details, ProOutsourcingDeliveryRepository $proOutsourcing)
        {
        $this->repository     = $repository;
        $this->details        = $details;
        $this->proOutsourcing = $proOutsourcing;
        }
    public function list()
        {
        $data = $this->details->condition(request())->getGrid();
        return $data;
        }
    protected function uploadAttachment()
        {
        $data  = request()->toArray();
        $Order = $this->details->whereId($data['id'])->first();
        if ($Order->status_id == 2) {
            fail("财务已审核！无法修改");
            }
        return $this->details->autosave(['id' => $data['id'], 'attachments' => $data['attachments']]);
        }
    protected function save($request)
        {
        $data = $request->toArray();
        if (isNotEmpty($data['id'] ?? "")) {
            fail("禁止编辑！必须删除后重新创建！");
            }

        $res = $this->repository->autosave($data);

        if ($res->status_id == 1) {
            fail("已审核。禁止编辑！");
            }
        $res->details->count() == 0 && fail("入库单明细为空，不能保存！");
        //附件就一个，保存到货单，只能一次保存一条
        $att = $data['details'][0]['attachments'] ?? null;

        $is_outsourcing_ids = [];
        $res->details->filter(function ($row) use ($res, &$is_outsourcing_ids, $data, $att)
            {
            if (isEmpty($row->lot_name ?? "")) {
                fail("批号必选！");
                }
            if (!is_numeric($row->quantity) || $row->quantity <= 0) {
                fail("数量不可以小于等于0");
                }

            if (!is_numeric($row->fect_quantity) || $row->fect_quantity <= 0) {
                fail("数量不可以小于等于0");
                }
            if (!is_numeric($row->amount) || $row->amount < 0) {
                fail("单价金额不可以小于0");
                }
            $row->se_quantity = $row->quantity;
            $row->se_price    = $row->price;
            $row->se_amount   = $row->amount;

            if ($row->target_id == 2) {
                if (isEmpty($row->outfactory_id) || isEmpty($row->outtype_id) || isEmpty($row->bom_id)) {
                    fail("采购直发需要填写外发相关信息");
                    }
                //更改库存位置
                $row->location_id     = $row->outfactory->getLocation(1);
                $is_outsourcing_ids[] = $row->id;
                }

            //设置剩余数量
            $row->remain_quantity = $row->quantity;
            $row->code            = $res->code;
            // $row->fect_quantity           = 0;
            // $row->fect_auxiliary_quantity = 0;
            $row->status_id = 0;
            //派车问题
            if (isNotEmpty($data['details'][0]['car'])) {
                $row['car'] = $data['details'][0]['car'];
                }
            $row['attachments'] = $att;
            $row                = $this->details->autosave($row);
            //运输 target_id == 1 入库，否则是外发 
            $row->car_id > 0 && $row->addCarItem($row->company->name, $row->target_id == 1 ? $row->location->name : $row->outfactory->name);
            //设置订单剩余可入库数量
            $order                  = $row->purchase_order;
            $order->remain_quantity -= $row->remain_quantity;
            $order->recive_quantity += $row->remain_quantity;
            if ($order->remain_quantity <= 0) {
                $order->status_id = 2;
                }
            $order->save();
            });

        if (count($is_outsourcing_ids) > 0) {
            $details = $this->audit($is_outsourcing_ids);
            //创建外发单
            $this->createOutSourcing($details[0]);
            }

        return $res;
        }

    public function createOutSourcing($details)
        {

        $details->filter(function ($row)
            {

            $data                         = [];
            $row['md_auxiliary_quantity'] = $row['fect_auxiliary_quantity'];
            $row['md_quantity']           = $row['fect_quantity'];
            $row['price']                 = $row['outsourcing_price'];
            $row['relation_code']         = $row['code'];
            $row['relation_code']         = $row['code'];
            $row['new_mpc_detail_id']     = $row['mpc_detail_id'];
            $row['relation_id']           = $row['id'];
            $row['amount']                = $row['price'] * $row['md_quantity'];

            $data['billdate']      = $row['billdate'];
            $data['outfactory_id'] = $row['outfactory_id'];
            $data['bom_id']        = $row['bom_id'];
            $data['price']         = $row['outsourcing_price'];
            $data['outtype_id']    = $row['outtype_id'];

            $data['remark'] = $row['remark'];
            unset($row['id']);
            $data['details'] = [$row];

            $this->proOutsourcing->autosave($data);
            });
        }
    protected function faudit()
        {
        $financeremark = request("financeremark");
        $this->getMain()->filter(function ($order) use ($financeremark)
            {
            if ($order->status_id != 1) {
                fail("单据【{$order->code}】【{$order->status->name}】,审核失败！");
                }
            $order->financeremark = $financeremark;
            $order->details->filter(function ($v) use ($financeremark)
                {
                $v->financeremark = $financeremark;
                $v->save();
                });
            $order->finance();
            });
        }
    protected function nofaudit()
        {
        $this->getMain()->filter(function ($order)
            {
            if ($order->status_id != 2) {
                fail("单据【{$order->code}】【{$order->status->name}】,审核失败！");
                }
            $order->nofinance();
            });
        }
    protected function audit($ids = null)
        {
        return $this->getMain($ids)->map(function ($Arrival)
            {
            if ($Arrival->status_id != 0)
                fail("单据【{$Arrival->code}】状态【{$Arrival->status->name}】审核失败！");
            auditSave($Arrival);
            return $Arrival->details->map(
                function ($v) use ($Arrival)
                    {
                    if ($v->instorage_way->type_id == 1) {
                        //委外加工先从外加工厂出库！
                        if ($v->old_location_id > 0)
                            $v->subStorage("old_mpc_detail");
                        if (($v->fect_quantity ?? 0) == 0) {
                            fail("入库数量不可以为0！");
                            }
                        $summary_storage_id      = $v->addStorage($v->instorage_way->name, $Arrival->code, $v->fect_quantity, $v->fect_auxiliary_quantity)->summary_storage_id;
                        $v['in_date']            = date('Y-m-d H:i:s');
                        $v['in_creator_id']      = auth()->user()->employee_id;
                        $v['summary_storage_id'] = $summary_storage_id;
                        }
                    else if ($v->instorage_way->type_id == -1) {
                        //4是采购折价
                        if ($Arrival->complaint_id != 4)
                            $v->subStorage();
                        $v['in_date'] = date('Y-m-d H:i:s');
                        }
                    auditSave($v);
                    return $v;
                    }
            );
            });
        }

    protected function noaudit()
        {
        return $this->getMain()->filter(function ($Arrival)
            {
            if ($Arrival->status_id != 1)
                fail("单据【{$Arrival->code}】【{$Arrival->status->name}】反审核失败！");
            auditSave($Arrival, false);
            $Arrival->details->filter(
                function ($v) use ($Arrival)
                    {
                    $v['in_date']       = null;
                    $v['in_creator_id'] = 0;
                    if ($v->target_id == 2) {
                        fail("采购直发不可以反审核！");
                        }
                    if ($v->instorage_way->type_id == 1) {
                        //委外加工先取消入库！
                        if ($v->old_location_id > 0)
                            $v->nosubStorage("old_mpc_detail");
                        $v->noaddStorage();
                        }
                    else if ($v->instorage_way->type_id == -1) {
                        //4是采购折价,没有库存操作
                        if ($Arrival->complaint_id != 4)
                            $v->nosubStorage();
                        }

                    auditSave($v, false);
                    }
            );
            });
        }
    public function getMain($ids = null)
        {
        $ids = $this->details->whereIn("id", $ids ?? $this->getRequestIds())->pluck("main_id");

        return $this->repository->whereIn("id", $ids)->get();
        }
    protected function delete($ids = null)
        {
        $main_ids = [];
        $this->details->whereIn("id", $ids ?? $this->getRequestIds())->get()->filter(function ($detail) use (&$main_ids)
            {
            //外发可以直接删除
            if ($detail->status_id == 1 && $detail->target_id != 2)
                fail("单据已审核！");
            $main_ids[$detail['main_id']] = $detail['main_id'];
            //是采购的设置订单剩余可入库数量

            $order = $detail->purchase_order;
            if ($order) {
                $order->remain_quantity += $detail->remain_quantity;
                $order->recive_quantity -= $detail->remain_quantity;
                if ($order->remain_quantity > 0) {
                    $order->status_id = 1;
                    }
                $order->save();
                }
            //是直发，删除外发,外发无法反审核
            if ($detail->target_id == 2) {
                $detail->noaddStorage();
                $detail->out_sourcing->main->delete();
                $detail->out_sourcing->delete();
                }
            //入库
            if ($detail->instorage_way->type_id == 1) {
                //委外加工先从外加工厂出库！
                if ($detail->old_mpc_detail_id > 0)
                    $detail->nouseStorage("old_mpc_detail");
                }
            //出库
            if ($detail->instorage_way->type_id == -1) {
                $detail->nouseStorage();
                }
            // $detail->target_id == 2 && 
            $moisture = $detail->moisture;
            if ($moisture) {
                $moisture->details->filter(fn($v) => $v->delete());
                $moisture->delete();
                }
            $detail->delete();
            });
        $newids = $this->details->whereIn("main_id", $main_ids)->pluck("main_id");
        $this->repository
            ->whereIn("id", $main_ids)
            ->whereNotIn("id", $newids)->get()->filter(function ($storage)
                {
                $storage->delete();
                });
        return $main_ids;
        // $this->details->delete($request->input("ids"));
        }
    }